package com.tengju.data.infrastructure.repository.clickhouse.crm;

import com.tengju.data.domain.model.analysis.Row;
import com.tengju.data.domain.model.clickhouse.CrowdAnalysisRepository;
import com.tengju.data.domain.model.cqrs.CrowdListFormQO;
import com.tengju.data.domain.shared.BasePage;
import com.tengju.data.domain.shared.Month;
import com.tengju.data.infrastructure.persistence.mybatis.mapper.clickhouse.crm.DwsCrmUserTagMapper;
import com.tengju.support.infrastructure.aop.MonitorTime;
import com.tengju.user.domain.model.user.UserIdCode;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import org.springframework.util.CollectionUtils;

import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @author chenhang
 * @Date 2021/5/6
 */
@Repository
@RequiredArgsConstructor(onConstructor_ = {@Autowired})
@Slf4j
public class CrowdAnalysisRepositoryImpl implements CrowdAnalysisRepository {

    private final DwsCrmUserTagMapper dwsCrmUserTagMapper;

    @Override
    public List<Row> tagList(List<UserIdCode> genSecIdCodes) {
        if (CollectionUtils.isEmpty(genSecIdCodes)) {
            return Collections.emptyList();
        }
        List<Long> idCodes = genSecIdCodes.stream()
                .map(UserIdCode::getValue)
                .collect(Collectors.toList());
        List<HashMap<String,Object>> sqlResult = dwsCrmUserTagMapper.tagList(idCodes);
        if (CollectionUtils.isEmpty(sqlResult)) {
            return Collections.emptyList();
        }
        return sqlResult.stream().map(Row::new)
                .collect(Collectors.toList());
    }

    @Override
    @MonitorTime
    public BasePage<Row> list(List<UserIdCode> genSecIdCodes,
                              Long idCode,
                              Long belongEcIdCode,
                              Long belongGenSecIdCode,
                              Long belongServiceProviderIdCode,
                              boolean isDirect,
                              String tagName,
                              String tagValue,
                              Integer offset,
                              Integer pageSize,
                              String orderColumn,
                              String orderType,
                              Month curMonth,
                              Month lastMonth,
                              List<Month> months) {
        BasePage<Row> pageResult = new BasePage<>();
        if (CollectionUtils.isEmpty(genSecIdCodes)) {
            pageResult.setTotal(0);
            return pageResult;
        }
        List<Long> genSecIdCodeValues = genSecIdCodes.stream()
                .map(UserIdCode::getValue)
                .collect(Collectors.toList());
        List<Integer> monthIntList = months.stream()
                .map(Month::getMonthInt)
                .collect(Collectors.toList());
        List<HashMap<String,Object>> sqlResult = dwsCrmUserTagMapper.list(
                genSecIdCodeValues,
                idCode,
                belongEcIdCode,
                belongGenSecIdCode,
                belongServiceProviderIdCode,
                isDirect,
                tagName,
                tagValue,
                offset,
                pageSize,
                orderColumn,
                orderType,
                curMonth.getMonthInt(),
                lastMonth.getMonthInt(),
                monthIntList
                );
        if (CollectionUtils.isEmpty(sqlResult)) {
            pageResult.setTotal(0);
            return pageResult;
        }
        int count = dwsCrmUserTagMapper.count(genSecIdCodeValues,
                idCode,
                belongEcIdCode,
                belongGenSecIdCode,
                belongServiceProviderIdCode,
                isDirect,
                tagName,
                tagValue,
                curMonth.getMonthInt(),
                lastMonth.getMonthInt(),
                monthIntList);
        pageResult.setTotal(count);
        List<Row> rows = sqlResult.stream().map(Row::new)
                .collect(Collectors.toList());
        pageResult.setDatas(rows);
        pageResult.setTotal(rows.size());
        return pageResult;
    }

    @Override
    @MonitorTime
    public BasePage<Row> list(CrowdListFormQO qo) {
        BasePage<Row> pageResult = new BasePage<>();
        if (qo == null || CollectionUtils.isEmpty(qo.getGenSecIdCodes())) {
            pageResult.setTotal(0);
            return pageResult;
        }
        List<Long> genSecIdCodeValues = qo.getGenSecIdCodes().stream()
                .map(UserIdCode::getValue)
                .collect(Collectors.toList());
        List<Integer> monthIntList = qo.getQueryMonthList().stream()
                .map(Month::getMonthInt)
                .collect(Collectors.toList());
        List<HashMap<String,Object>> sqlResult = dwsCrmUserTagMapper.list(
                genSecIdCodeValues,
                qo.getIdCode(),
                qo.getBelongEcIdCode(),
                qo.getBelongGenSecIdCode(),
                qo.getBelongServiceProviderIdCode(),
                qo.isDirect(),
                qo.getTagName(),
                qo.getTagValue(),
                qo.getOffset(),
                qo.getPageSize(),
                qo.getOrderColumn(),
                qo.getOrderType(),
                qo.getCurMonth().getMonthInt(),
                qo.getLastMonth().getMonthInt(),
                monthIntList
        );
        if (CollectionUtils.isEmpty(sqlResult)) {
            pageResult.setTotal(0);
            return pageResult;
        }
        int count = dwsCrmUserTagMapper.count(genSecIdCodeValues,
                qo.getIdCode(),
                qo.getBelongEcIdCode(),
                qo.getBelongGenSecIdCode(),
                qo.getBelongServiceProviderIdCode(),
                qo.isDirect(),
                qo.getTagName(),
                qo.getTagValue(),
                qo.getCurMonth().getMonthInt(),
                qo.getLastMonth().getMonthInt(),
                monthIntList);
        pageResult.setTotal(count);
        List<Row> rows = sqlResult.stream().map(Row::new)
                .collect(Collectors.toList());
        pageResult.setDatas(rows);
        return pageResult;
    }
}
